/*******************************************************************************
 * Copyright (c) 陈华(clinker@163.com).
 * All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *******************************************************************************/
package com.boot2.core.utils;

import org.apache.commons.codec.DecoderException;
import org.apache.commons.codec.binary.Hex;

import java.io.UnsupportedEncodingException;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.CharBuffer;
import java.nio.charset.Charset;
import java.nio.charset.CharsetDecoder;

/**
 * 字节、字节数组与其他数据类型的转换。
 */
public abstract class ByteUtils {

    /**
     * 字节数字对应ascii码十进制数字，转换出对应的字符,如38对应&,所以ascii码上的字符转换成字节数组后，再通过此方法转回字符正常，但是中文不支持
     *
     * @param arrB
     * @return
     */
//    public static String byteArr2HexStr(byte[] arrB) {
//        int iLen = arrB.length;
//        // 每个byte用两个字符才能表示，所以字符串的长度是数组长度的两倍
//        StringBuffer sb = new StringBuffer(iLen);
//        for (int i = 0; i < iLen; i++) {
//            int intTmp = arrB[i];
//            // 把负数转换为正数
//            while (intTmp < 0) {
//                intTmp = intTmp + 256;
//            }
//            // 小于0F的数需要在前面补0
//            if (intTmp < 16) {
//                sb.append("0");
//            }
//            if (intTmp == 48) {
//                sb.append("0");
//            } else {
//                sb.append(convertHexToString(Integer.toString(intTmp, 16)));
//            }
//            // sb.append(Integer.toString(intTmp, 16));
//        }
//        return sb.toString();
//    }

    ;

    /**
     * 将byte数组转换为表示16进制值的字符串， 如：byte[]{8,18}转换为：0813， 和public static byte[]
     * hexStr2ByteArr(String strIn) 互为可逆的转换过程
     *
     * @param arrB 需要转换的byte数组
     * @return 转换后的字符串
     */

    public static String convertHexToString(String hex) {

        StringBuilder sb = new StringBuilder();
        StringBuilder temp = new StringBuilder();

        // 49204c6f7665204a617661 split into two characters 49, 20, 4c...
        for (int i = 0; i < hex.length() - 1; i += 2) {

            // grab the hex in pairs
            String output = hex.substring(i, (i + 2));
            // convert hex to decimal
            int decimal = Integer.parseInt(output, 16);
            // convert the decimal to character
            sb.append((char) decimal);

            temp.append(decimal);
        }

        return sb.toString();
    }

    // 16进制字符串转ASCII码

    /**
     * 把大端序字节数组转换成小端序，然后转换成整数。
     *
     * @param b 字节数组
     * @return 整数
     */
    public static int bigEndianToInt(byte[] b) {
        return bigEndianToInt(b, 0, b.length);
    }

    /**
     * 把大端序字节数组从索引offset开始，长度为length的字节，转换成小端序，然后转换成整数。
     *
     * @param b      字节数组
     * @param offset 开始索引在字节数组里的偏移量
     * @param size   字节长度
     * @return 整数
     */
    public static int bigEndianToInt(byte[] b, int offset, int size) {
        final ByteBuffer buf = ByteBuffer.wrap(b, offset, size).order(ByteOrder.LITTLE_ENDIAN);
        switch (size) {
            case 2:
                return buf.getShort();
            case 4:
                return buf.getInt();
            default:
                throw new IllegalArgumentException("Size must be 2 or 4!");
        }
    }

    /**
     * 大端序字节数组转换为小端序字节数组。
     *
     * @param b 大端序字节数组
     * @return 小端序字节数组
     */
    public static byte[] bigEndianToLittleEndian(byte[] b) {
        return reverse(b);
    }

    /**
     * 将大端序字节数组从索引offset开始，长度为length的字节，转换为小端序字节数组。
     *
     * @param b      大端序字节数组
     * @param offset 开始索引在字节数组里的偏移量
     * @param size   字节长度
     * @return 小端序字节数组
     */
    public static byte[] bigEndianToLittleEndian(byte[] b, int offset, int size) {
        return reverse(b, offset, size);
    }

    /**
     * Convert a byte array (or part thereof) into an integer. The byte array should
     * be in big-endian form. That is, the byte at index 'offset' should be the
     * MSB(most significant bit).
     *
     * @param b      The array containing the bytes
     * @param offset The array index of the MSB
     * @param size   The number of bytes to convert into the integer
     * @return An integer value represented by the specified bytes.
     */
    public static int bytesToInt(byte[] b, int offset, int size) {
        int num = 0;
        int sw = 8 * (size - 1);
        for (int loop = 0; loop < size; loop++) {
            num |= (b[offset + loop] & 0x00ff) << sw;
            sw -= 8;
        }
        return num;
    }

    /**
     * Convert a byte array (or part thereof) into a long. The byte array should be
     * in big-endian form. That is, the byte at index 'offset' should be the MSB.
     *
     * @param b      The array containing the bytes
     * @param offset The array index of the MSB
     * @param size   The number of bytes to convert into the long
     * @return An long value represented by the specified bytes.
     */
    public static long bytesToLong(byte[] b, int offset, int size) {
        long num = 0;
        long sw = 8L * (size - 1L);

        for (int loop = 0; loop < size; loop++) {
            num |= ((long) b[offset + loop] & 0x00ff) << sw;
            sw -= 8;
        }
        return num;
    }

    /**
     * 长整数转换为字节数组。
     *
     * @param num    被转换的长整数
     * @param offset 开始索引在字节数组里的偏移量
     * @param size   字节长度
     * @return 字节数组
     */
    public static byte[] longToBytes(long num, int offset, int size) {
        final byte[] b = new byte[size];
        long sw = (size - 1) * 8;
        long mask = 0xffL << sw;
        for (int l = 0; l < size; l++) {
            b[offset + l] = ((byte) ((num & mask) >>> sw));
            sw -= 8;
            mask >>>= 8;
        }
        return b;
    }

    public static byte[] intToByteArray(final int integer) {
        int byteNum = (40 - Integer.numberOfLeadingZeros(integer < 0 ? ~integer : integer)) / 8;
        byte[] byteArray = new byte[4];

        for (int n = 0; n < byteNum; n++) {
            byteArray[3 - n] = (byte) (integer >>> (n * 8));
        }

        return (byteArray);
    }

    /**
     * int to byte[] 支持 1或者 4 个字节,默认为大端，即大的字节放前面
     *
     * @param i
     * @param len
     * @return
     */
    public static byte[] intToByte(int i, int len) {
        byte[] abyte = null;
        if (len == 1) {
            abyte = new byte[len];
            abyte[0] = (byte) (0xff & i);
        } else {
            abyte = new byte[len];
            abyte[0] = (byte) (0xff & i);
            abyte[1] = (byte) ((0xff00 & i) >> 8);
            abyte[2] = (byte) ((0xff0000 & i) >> 16);
            abyte[3] = (byte) ((0xff000000 & i) >> 24);
        }
        return abyte;
    }

    /**
     * int to byte[] 支持 1或者 4 个字节,控制大小端
     *
     * @param i
     * @param len
     * @param endian 控制大小端
     * @return
     */
    public static byte[] intToByte(int i, int len, LITTLE_BIG_ENDIAN endian) {
        byte[] abyte = null;
        if (len == 1) {
            abyte = new byte[len];
            abyte[0] = (byte) (0xff & i);
        } else {
            abyte = new byte[len];
            abyte[0] = (byte) (0xff & i);
            abyte[1] = (byte) ((0xff00 & i) >> 8);
            abyte[2] = (byte) ((0xff0000 & i) >> 16);
            abyte[3] = (byte) ((0xff000000 & i) >> 24);
        }
        //如果指定为小端，则字节反转
        if (endian == LITTLE_BIG_ENDIAN.LITTLE) {
            abyte = reverse(abyte);
        }
        return abyte;
    }

    /**
     * 16进制字符串转int
     *
     * @param hexStr
     * @return
     */
    public static Integer hexString2UnsignedInt(String hexStr) {
        int ret = Integer.parseInt(hexStr, 16);
        ret = ((ret & 0x8000) > 0) ? (ret - 0x10000) : (ret);
        return ret;
    }

    /**
     * 获取高四位
     *
     * @param data
     * @return
     */
    public static int getHeight4(byte data) {
        int height;
        height = ((data & 0xf0) >> 4);
        return height;
    }

    /**
     * 获取低四位
     *
     * @param data
     * @return
     */
    public static int getLow4(byte data) {
        int low;
        low = (data & 0x0f);
        return low;
    }

    /**
     * 16进制字符串转int, 无符号的int
     *
     * @param hexStr
     * @return
     */
    public static Integer hexByte2UnsignedInt(byte[] byteArr) {
        return hexString2UnsignedInt(Hex.encodeHexString(byteArr));
    }

    /**
     * 无符号的int转16进制字符串,
     *
     * @param value
     * @param length 取后面几个字节
     * @return
     */
    public static String unsignedInt2HexString(int value, int length) {
//        String hex = Integer.toHexString(value & 0xFF);
        String hex = Integer.toHexString(value);
        int length1 = hex.length();
        length = length * 2;
        if (length <= length1) {
            int start = length1 - length;
            return hex.substring(start, length1);
        } else {
            int diff = length - length1;
            String t0 = "";
            for (int i = 0; i < diff; i++) {
                t0 += "0";
            }
            return t0 + hex;
        }
    }

    /**
     * 无符号的int转16进制字节,两位
     *
     * @param value
     * @param length 取后面几个字节
     * @return
     */
    public static byte[] unsignedInt2HexByte(int value, int length) {
        try {
            String str = unsignedInt2HexString(value, length);
            //此时已经是16进制字符串
            return Hex.decodeHex(str.toCharArray());
        } catch (DecoderException e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 无符号的int转16进制字符串,
     *
     * @param value
     * @return
     */
    public static String unsignedInt2HexString(int value) {
//        String hex = Integer.toHexString(value & 0xFF);
        String hex = Integer.toHexString(value);
        return hex;
    }

    /**
     * 无符号的int转16进制字节,两位
     *
     * @param value
     * @return
     */
    public static byte[] unsignedInt2HexByte(int value) {
        try {
            String str = unsignedInt2HexString(value);
            return Hex.decodeHex(str.toCharArray());
        } catch (DecoderException e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 16进制字节转正整型
     *
     * @param byteArr
     * @return
     */
    public static Integer hexByte2Int(byte[] byteArr) {
        return Integer.parseInt(Hex.encodeHexString(byteArr), 16);
    }

    /**
     * 16进制字符串转正整型
     *
     * @param byteArr
     * @return
     */
    public static Integer hexHex2Int(String hexString) {
        return Integer.parseInt(hexString, 16);
    }

    /**
     * int转16进制字符串
     *
     * @param i
     * @param len
     * @param endian
     * @return
     */
    public static String intToHexString(int i, int len, LITTLE_BIG_ENDIAN endian) {
        byte[] byte1 = intToByte(i, len, endian);
        return Hex.encodeHexString(byte1);
    }

    /**
     * 字节逆序排序。
     *
     * @param b 字节数组
     * @return 逆序后的字节数组
     */
    public static byte[] reverse(byte[] b) {
        return reverse(b, 0, b.length);
    }

    /**
     * 将字节数组从索引offset到offset+length之间的字节反转顺序。
     *
     * @param b      字节数组
     * @param offset 开始索引在字节数组里的偏移量
     * @param size   字节长度
     * @return 逆序后的字节数组
     */
    public static byte[] reverse(byte[] b, int offset, int size) {
        final byte[] result = new byte[size];
        for (int i = 0; i < size; i++) {
            result[i] = b[offset + size - i - 1];
        }
        return result;
    }

    public static String hexBytes2HexString(byte[] b) {
//		String ret = "";
//		for (int i = 0; i < b.length; i++) {
//			String hex = Integer.toHexString(b[i] & 0xFF);
//			ret += hex.toUpperCase();
//		}
        String str = Hex.encodeHexString(b);
        return str.toUpperCase();
    }

    // 字节反转eg:12345678AABBCCDD--->DDCCBBAA78563412
    public static byte[] byteReversal(String station_id) {
        byte[] station_id_bytes = null;
        try {
            String[] station_id_str = new String[station_id.length() / 2];
            for (int i = 0; i < station_id.length(); ) {
                station_id_str[i / 2] = station_id.substring(i, i + 2);
                i += 2;
            }
            StringBuilder builder = new StringBuilder();
            for (int j = station_id_str.length - 1; j >= 0; j--) {
                builder.append(station_id_str[j]);
            }
            station_id_bytes = builder.toString().getBytes();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return station_id_bytes;
    }

    /**
     * char转成字节
     *
     * @param c
     * @return
     */
    // public static byte[] getBytes(char c) {
    // byte[] b = new byte[2];
    // b[0] = (byte) ((c & 0xFF00) >> 8);
    // b[1] = (byte) (c & 0xFF);
    // return b;
    // }
    public static byte[] getBytes(char[] chars) {
        Charset cs = Charset.forName("UTF-8");
        CharBuffer cb = CharBuffer.allocate(chars.length);
        cb.put(chars);
        cb.flip();
        ByteBuffer bb = cs.encode(cb);

        return bb.array();
    }

    public static char[] getChars(byte[] bytes) {
        Charset cs = Charset.forName("UTF-8");
        ByteBuffer bb = ByteBuffer.allocate(bytes.length);
        bb.put(bytes);
        bb.flip();
        CharBuffer cb = cs.decode(bb);

        return cb.array();
    }

    /**
     * 短整型转字节数组
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(short data) {
        byte[] bytes = new byte[2];
        bytes[0] = (byte) (data & 0xff);
        bytes[1] = (byte) ((data & 0xff00) >> 8);
        return bytes;
    }

    // ================

    /**
     * char字符转字节数组
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(char data) {
        byte[] bytes = new byte[2];
        bytes[0] = (byte) (data);
        bytes[1] = (byte) (data >> 8);
        return bytes;
    }

    /**
     * 把字符转为int
     *
     * @param c
     * @return
     */
    public static int getByte(char c) {
        String string = "0123456789ABCDEF";
        for (int i = 0; i < string.length(); i++) {
            if (string.charAt(i) == c) {
                return i;
            }
        }
        return -1;
    }

    /**
     * 整型转字节数组(4字节小端)
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(int data) {
        byte[] bytes = new byte[4];
        bytes[0] = (byte) (data & 0xff);
        bytes[1] = (byte) ((data & 0xff00) >> 8);
        bytes[2] = (byte) ((data & 0xff0000) >> 16);
        bytes[3] = (byte) ((data & 0xff000000) >> 24);
        return bytes;
    }

    /**
     * 整型转字节数组(4字节大端)
     *
     * @param data
     * @return
     */
    public static byte[] getBytesBig(int data) {
        byte[] bytes = new byte[4];
        bytes[0] = (byte) ((data & 0xff000000) >> 24);
        bytes[1] = (byte) ((data & 0xff0000) >> 16);
        bytes[2] = (byte) ((data & 0xff00) >> 8);
        bytes[3] = (byte) (data & 0xff);
        return bytes;
    }

    /**
     * 长整型转为字节数组
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(long data) {
        byte[] bytes = new byte[8];
        for (int i = 8; i > 0; i--) {
            bytes[8 - i] = (byte) ((data >> ((8 - i) * 8)) & 0xff);
        }
        /***
         * bytes[0] = (byte) (data & 0xff); bytes[1] = (byte) ((data >> 8) & 0xff);
         * bytes[2] = (byte) ((data >> 16) & 0xff); bytes[3] = (byte) ((data >> 24) &
         * 0xff); bytes[4] = (byte) ((data >> 32) & 0xff); bytes[5] = (byte) ((data >>
         * 40) & 0xff); bytes[6] = (byte) ((data >> 48) & 0xff); bytes[7] = (byte)
         * ((data >> 56) & 0xff);
         ***/
        return bytes;
    }

    /**
     * 单精度（符点数）转为字节数组(小端)
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(float data) {
        int intBits = Float.floatToIntBits(data);
        return getBytes(intBits);
    }

    public static String byteBufferToString(ByteBuffer buffer) {
        CharBuffer charBuffer = null;
        try {
            Charset charset = Charset.forName("UTF-8");
            CharsetDecoder decoder = charset.newDecoder();
            charBuffer = decoder.decode(buffer);
            buffer.flip();
            return charBuffer.toString();
        } catch (Exception ex) {
            ex.printStackTrace();
            return null;
        }
    }

    /**
     * 符点数转字节数组
     *
     * @param data
     * @param byteOrder 大小端类型,默认小端
     * @return
     */
    public static byte[] getBytes(float data, ByteOrder byteOrder) {
        int intBits = Float.floatToIntBits(data);
        if (byteOrder == ByteOrder.BIG_ENDIAN) {
            return getBytesBig(intBits);
        } else {
            return getBytes(intBits);
        }
    }

    /**
     * 双精度转为字节数组
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(double data) {
        long intBits = Double.doubleToLongBits(data);
        return getBytes(intBits);
    }

    /**
     * 字符串转为字节数组
     *
     * @param data
     * @param charsetName 编码如utf-8
     * @return
     */
    public static byte[] getBytes(String data, String charsetName) {
        Charset charset = Charset.forName(charsetName);
        return data.getBytes(charset);
    }

    /**
     * 字符串转为字节数组
     *
     * @param data
     * @return
     */
    public static byte[] getBytes(String data) {
        return getBytes(data, "utf-8");
    }

    /**
     * 字节数组转为短整型
     *
     * @param bytes
     * @return
     */
    public static short getShort(byte[] bytes) {
        return (short) ((0xff & bytes[0]) | (0xff00 & (bytes[1] << 8)));
    }

    /**
     * 字节数组转为字符
     *
     * @param bytes
     * @return
     */
    public static char getChar(byte[] bytes) {
        return (char) ((0xff & bytes[0]) | (0xff00 & (bytes[1] << 8)));
    }

    /**
     * 字节数组转为整型
     *
     * @param bytes
     * @return
     */
    public static int getInt(byte[] bytes) {
        return (0xff & bytes[0]) | (0xff00 & (bytes[1] << 8)) | (0xff0000 & (bytes[2] << 16))
                | (0xff000000 & (bytes[3] << 24));
    }

    /**
     * 字节数组转为长整型
     *
     * @param bytes
     * @return
     */
    public static long getLong(byte[] bytes) {
        return (0xffL & bytes[0]) | (0xff00L & ((long) bytes[1] << 8)) | (0xff0000L & ((long) bytes[2] << 16))
                | (0xff000000L & ((long) bytes[3] << 24)) | (0xff00000000L & ((long) bytes[4] << 32))
                | (0xff0000000000L & ((long) bytes[5] << 40)) | (0xff000000000000L & ((long) bytes[6] << 48))
                | (0xff00000000000000L & ((long) bytes[7] << 56));
    }

    /**
     * 字节数组转为单精度（符点数） 小端
     *
     * @param bytes
     * @return
     */
    public static float getFloat(byte[] bytes) {
        return Float.intBitsToFloat(getInt(bytes));
    }

    /**
     * 字节数组转为双精度
     *
     * @param bytes
     * @return
     */
    public static double getDouble(byte[] bytes) {
        long l = getLong(bytes);
        return Double.longBitsToDouble(l);
    }

    /**
     * 字节数组转为字符串
     *
     * @param bytes
     * @param charsetName
     * @return
     */
    public static String getString(byte[] bytes, String charsetName) {
        return new String(bytes, Charset.forName(charsetName));
    }

    /**
     * 字节数组转为字符串
     *
     * @param bytes
     * @return
     */
    public static String getString(byte[] bytes) {
        return getString(bytes, "utf-8");
    }


    /**
     * 高低位反转
     *
     * @param s
     * @return
     */
    public static String reversion(String s) {
        int len = s.length();
        char[] chars = s.toCharArray();
        StringBuffer sb = new StringBuffer(8);
        int i = len - 1;
        while (i >= 0) {
            sb.append(chars[i - 1]);
            sb.append(chars[i]);
            i -= 2;
        }
        return sb.toString();
    }

    /**
     * 16进制字符串转为字节数组
     */
    public static byte[] hexString2Bytes(String hexString) {
        if (hexString == null || hexString.equals("")) {
            return null;
        }
        hexString = hexString.toUpperCase();
        int length = hexString.length() / 2;
        char[] hexChars = hexString.toCharArray();
        byte[] d = new byte[length];
        for (int i = 0; i < length; i++) {
            int pos = i * 2;
            d[i] = (byte) (getByte(hexChars[pos]) << 4 | getByte(hexChars[pos + 1]));
        }
        return d;
    }

//     /**
//     * 字符数组转为16进制字符串
//     */
//     public static String hexBytes2HexString2(byte[] src) {
//     StringBuilder stringBuilder = new StringBuilder("");
//     if (src == null || src.length <= 0) {
//     return null;
//     }
//     for (int i = 0; i < src.length; i++) {
//     int v = src[i] & 0xFF;
//     String hv = Integer.toHexString(v);
//     if (hv.length() < 2) {
//     stringBuilder.append(0);
//     }
//     stringBuilder.append(hv);
//     }
//     return stringBuilder.toString();
//     }

    public static void floatAndByte() {
        float f = 10.56f;
        byte[] fb = getBytes(f);
        ByteBuffer bb1 = ByteBuffer.wrap(fb);
        for (byte bt : bb1.array()) {
            System.out.printf("%x", bt);
        }
        float ft = getFloat(fb);
        System.out.println();
        System.out.println(ft);
        String hex = "4128f5c3";
        int i = Integer.parseInt(hex, 16);
        System.out.println(Float.intBitsToFloat(i));
        hex = "c3f52841";
        hex = reversion(hex);
        i = Integer.parseInt(hex, 16);
        System.out.println(Float.intBitsToFloat(i));
        System.out.println(Float.intBitsToFloat(i));
    }

    public static void main(String[] args) {
        short s = 32767;
        int i = 1024;
        long l = 1024;
        char c = 'a';
        float f = 10.22f;
        double d = 10.22;
        String string = "字节数组与各类型互转的实例";
        System.out.println(s);
        System.out.println(i);
        System.out.println(l);
        System.out.println(c);
        System.out.println(f);
        System.out.println(d);
        System.out.println(string);

        System.out.println("@#$%^&");

        System.out.println(getShort(getBytes(s)));
        System.out.println(getInt(getBytes(i)));
        System.out.println(getLong(getBytes(l)));
        System.out.println(getChar(getBytes(c)));
        System.out.println(getFloat(getBytes(f)));
        System.out.println(getDouble(getBytes(d)));
        System.out.println(getString(getBytes(string)));

        floatAndByte();
    }

    /**
     * 计算BCC校验值
     *
     * @param data
     * @return
     */
    public static String getBCC(byte[] data) {
        String ret = "";
        byte BCC[] = new byte[1];
        for (int i = 0; i < data.length; i++) {
            BCC[0] = (byte) (BCC[0] ^ data[i]);
        }
        String hex = Integer.toHexString(BCC[0] & 0xFF);
        if (hex.length() == 1) {
            hex = '0' + hex;
        }
        ret += hex.toUpperCase();
        return ret;
    }

    /**
     * 计算BCC校验值
     *
     * @param hex
     * @return
     */
    public static String getBCC(String hex) {
        int i = 0, j = 0;
        int len = hex.length();
        short inb[] = new short[len];
        for (i = 0; i < len; i++) {
            inb[i] = charToHex(hex.charAt(i));   //将String里的每一个char转换为Hex
        }

        for (i = 0; i < len; i++) {    //将每两个Hex合并成一个byte
            inb[j] = (byte) (((inb[i] << 4) & 0x00f0) | ((inb[i + 1]) & 0x000f));
            i++;
            j++;
        }
        byte temp = 0x00; //校验值
        for (i = 0; i < len / 2; i++) { //异或
            temp ^= inb[i];
        }
        byte[] bytes = new byte[1];
        bytes[0] = temp;
        return hexBytes2HexString(bytes);
    }

    public static short charToHex(char x) { //将单个char转换为Hex
        short result = 0;
        switch (x) {
            case 'a':
                result = 10;
                break;
            case 'b':
                result = 11;
                break;
            case 'c':
                result = 12;
                break;
            case 'd':
                result = 13;
                break;
            case 'e':
                result = 14;
                break;
            case 'f':
                result = 15;
                break;
            case 'A':
                result = 10;
                break;
            case 'B':
                result = 11;
                break;
            case 'C':
                result = 12;
                break;
            case 'D':
                result = 13;
                break;
            case 'E':
                result = 14;
                break;
            case 'F':
                result = 15;
                break;
            default:
                result = (short) Character.getNumericValue(x);
                break;
        }
        return result;
    }

    public void jugelizi() throws UnsupportedEncodingException {
        String s = Charset.defaultCharset().displayName();
        System.out.println("默认编码：" + s);
        String s1 = "我喜欢你,My Love";
        ByteBuffer bb1 = ByteBuffer.wrap(s1.getBytes("UTF-8"));
        for (byte bt : bb1.array()) {
            System.out.printf("%x", bt);
        }
        System.out.println();
        String s2 = Charset.forName("utf-8").decode(bb1).toString();
        System.out.println("1/" + s2);
        // char[]用法
        char[] chArray = {'I', 'L', 'o', 'v', 'e', '你'};
        // CharBuffer用法
        CharBuffer cb = CharBuffer.wrap(chArray);
        // 重新定位指针
        cb.flip();
        s2 = new String(chArray);
        System.out.println("2/" + s2);
        // ByteBuffer用法
        ByteBuffer bb2 = Charset.forName("utf-8").encode(cb);
        s2 = Charset.forName("utf-8").decode(bb2).toString();
        System.out.println("3/" + s2);
        // 利用Charset编码为指定字符集
        ByteBuffer bb3 = Charset.forName("utf-8").encode(s1);
        byte[] b = bb3.array();
        // 利用Charset按指定字符集解码为字符串
        ByteBuffer bb4 = ByteBuffer.wrap(b);
        s2 = Charset.forName("utf-8").decode(bb4).toString();
        System.out.println("4/" + s2);
    }


    /**
     * 大小端控制
     *
     * @author zhangweilin
     */
    public static enum LITTLE_BIG_ENDIAN {
        LITTLE,
        BIG
    }

}
